package com.gpframework.module.manufacture.service.impl;

import cn.hutool.core.convert.Convert;
import cn.hutool.core.lang.TypeReference;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.gpframework.common.enums.YesNoEnum;
import com.gpframework.common.exception.BaseException;
import com.gpframework.common.utils.DateUtils;
import com.gpframework.common.utils.StringUtils;
import com.gpframework.module.manufacture.domain.GpProductionDetails;
import com.gpframework.module.manufacture.domain.GpProductionScheduling;
import com.gpframework.module.manufacture.domain.req.GpProductionDetailsUpdate;
import com.gpframework.module.manufacture.domain.req.GpProductionSchedulingUpdate;
import com.gpframework.module.manufacture.domain.vo.GpProductionSchedulingVo;
import com.gpframework.module.manufacture.mapper.GpProductionSchedulingMapper;
import com.gpframework.module.manufacture.service.IGpProductionDetailsService;
import com.gpframework.module.manufacture.service.IGpProductionSchedulingService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;
/**
 * @ClassName GpProductionScheduling
 * @Author gpframework
 * @Date 2023-12-12
 * @Version 1.0.0
 * @Description 生产排单Service业务层处理
 */
@Service
public class GpProductionSchedulingServiceImpl extends ServiceImpl<GpProductionSchedulingMapper, GpProductionScheduling> implements IGpProductionSchedulingService {

    @Autowired
    private IGpProductionDetailsService iGpProductionDetailsService;

    /**
     * @Description 查询列表返回VO 用于返回给前端的列表接口
     * @Author gpframework
     * @Date 2023-12-12
     * @Param [lqw]
     * @Return List<GpProductionSchedulingVo>
     */
    @Override
    public List<GpProductionSchedulingVo> listVo(QueryWrapper<GpProductionScheduling> lqw) {
        return this.baseMapper.listVo(lqw);
    }

    /**
     * @Description 通过查询详情VO 用于返回给前端的列详情接口
     * @Author gpframework
     * @Date 2023-12-12
     * @Param [id]
     * @Return GpProductionSchedulingVo
     */
    @Override
    public GpProductionSchedulingVo getVoById(Long id) {
        return this.baseMapper.getVo(id);
    }

    ///**
    // * 生成生产排单表
    // * @param id
    // * @return
    // */
    //@Override
    //@Transactional
    //public boolean createProductionScheduling(Long id, String createBy) {
    //    GpProductionDetails gpProductionDetails = iGpProductionDetailsService.getById(id);
    //    if (gpProductionDetails == null) {
    //        return false;
    //    }
    //    // 更新做货明细表中的是否下单字段
    //    iGpProductionDetailsService.update(new UpdateWrapper<GpProductionDetails>().set("place_an_order_flag", YesNoEnum.YES.getKey()).eq("id", id));
    //    List<GpProductionScheduling> list = new ArrayList<>();
    //    // 获取缸数，有多少缸就生成多少条数据
    //    Integer dyeVatQuantity = gpProductionDetails.getDyeVatQuantity() == null ? 0 : gpProductionDetails.getDyeVatQuantity();
    //    for (int i = 1; i <= dyeVatQuantity; i++) {
    //        GpProductionScheduling gpProductionScheduling = Convert.convert(new TypeReference<GpProductionScheduling>() {}, gpProductionDetails);
    //        if (StringUtils.isNotBlank(createBy)) {
    //            gpProductionScheduling.setCreateBy(createBy);
    //        }
    //        gpProductionScheduling.setProductionDetailsId(gpProductionDetails.getId());
    //        if (gpProductionDetails.getSn() != null) {
    //            gpProductionScheduling.setSn(gpProductionDetails.getSn() + "-" + i);
    //        }
    //        gpProductionScheduling.setQuantity(null);
    //        Date now = new Date();
    //        gpProductionScheduling.setPlaceOrdersTime(now);
    //        gpProductionScheduling.setWarehouseEntryTime(now);
    //        gpProductionScheduling.setDyeVatNo(gpProductionDetails.getDyeVatNo());
    //        gpProductionScheduling.setLeaveGreyNum(gpProductionDetails.getLeaveGreyNum());
    //        this.init(gpProductionScheduling);
    //        list.add(gpProductionScheduling);
    //    }
    //    return this.saveBatch(list);
    //}


    @Override
    @Transactional
    public boolean createProductionScheduling(GpProductionDetailsUpdate gpProductionDetailsUpdate, String createBy) {
        GpProductionDetails gpProductionDetails = iGpProductionDetailsService.getById(gpProductionDetailsUpdate.getId());
        if (gpProductionDetails == null) {
            return false;
        }
        gpProductionDetails.setDyeVatNo(gpProductionDetailsUpdate.getDyeVatNo());
        if (gpProductionDetails.getLeaveGreyNum()<gpProductionDetailsUpdate.getActualGreyUsed()){
            throw new BaseException("可用胚布剩余数量不足");
        }
        //更新的胚布剩余数量
        gpProductionDetails.setId(gpProductionDetailsUpdate.getId());
        iGpProductionDetailsService.updateById(gpProductionDetails);
        // 更新做货明细表中的是否下单字段
        iGpProductionDetailsService.update(new UpdateWrapper<GpProductionDetails>().set("place_an_order_flag", YesNoEnum.YES.getKey()).eq("id", gpProductionDetailsUpdate.getId()));
        List<GpProductionScheduling> list = new ArrayList<>();
        // 获取缸数，有多少缸就生成多少条数据
        Integer dyeVatQuantity = gpProductionDetails.getDyeVatQuantity() == null ? 0 : gpProductionDetails.getDyeVatQuantity();
        for (int i = 1; i <= dyeVatQuantity; i++) {
            GpProductionScheduling gpProductionScheduling = Convert.convert(new TypeReference<GpProductionScheduling>() {}, gpProductionDetails);
            if (StringUtils.isNotBlank(createBy)) {
                gpProductionScheduling.setCreateBy(createBy);
            }
            gpProductionScheduling.setProductionDetailsId(gpProductionDetails.getId());
            if (gpProductionDetails.getSn() != null) {
                gpProductionScheduling.setSn(gpProductionDetails.getSn() + "-" + i);
            }
            gpProductionScheduling.setQuantity(null);
            Date now = new Date();
            gpProductionScheduling.setPlaceOrdersTime(gpProductionDetailsUpdate.getPlaceOrdersTime());
            gpProductionScheduling.setWarehouseEntryTime(now);
            gpProductionScheduling.setDyeVatNo(gpProductionDetailsUpdate.getDyeVatNo());
            gpProductionScheduling.setActualGreyUsed(gpProductionDetailsUpdate.getActualGreyUsed());

            this.init(gpProductionScheduling);
            list.add(gpProductionScheduling);
        }
        return this.saveBatch(list);
    }

    @Override
    public boolean edit(List<GpProductionSchedulingUpdate> list) {
        List<GpProductionScheduling> updateList = new ArrayList<>();
        for (GpProductionSchedulingUpdate gpProductionSchedulingUpdate : list) {

            GpProductionScheduling gpProductionScheduling = Convert.convert(new TypeReference<GpProductionScheduling>() {}, gpProductionSchedulingUpdate);
            this.init(gpProductionScheduling);
            //更新上一级数据（修改做货明细）
            this.updateProductionDetails(gpProductionScheduling);
            updateList.add(gpProductionScheduling);
        }
        return this.updateBatchById(updateList);
    }

    private void updateProductionDetails(GpProductionScheduling gpProductionScheduling) {
        GpProductionDetails gpProductionDetails = iGpProductionDetailsService.getById(gpProductionScheduling.getProductionDetailsId());

        //更新做货明细
        gpProductionDetails.setSn(gpProductionScheduling.getSn());
        gpProductionDetails.setDyeVatNo(gpProductionScheduling.getDyeVatNo());
        gpProductionDetails.setSupplierName(gpProductionScheduling.getSupplierName());
        gpProductionDetails.setSupplierGreyClothName(gpProductionScheduling.getSupplierGreyClothName());
        gpProductionDetails.setDyeingFactoryName(gpProductionScheduling.getDyeingFactoryName());
        gpProductionDetails.setProductName(gpProductionScheduling.getProductName());
        gpProductionDetails.setColour(gpProductionScheduling.getColour());
        gpProductionDetails.setFactoryColourCode(gpProductionScheduling.getFactoryColourCode());
        iGpProductionDetailsService.updateById(gpProductionDetails);

    }

    @Override
    public boolean editOne(GpProductionSchedulingUpdate gpProductionSchedulingUpdate) {
        GpProductionScheduling gpProductionScheduling = Convert.convert(new TypeReference<GpProductionScheduling>() {}, gpProductionSchedulingUpdate);
        this.init(gpProductionScheduling);
        return this.updateById(gpProductionScheduling);
    }

    @Override
    public boolean copy(Long id, Integer copyNum) {
        GpProductionScheduling gpProductionScheduling = this.getById(id);
        if (gpProductionScheduling == null) {
            return false;
        }
        for (int i = 0; i < copyNum; i++) {
            gpProductionScheduling.setId(null);
            GpProductionDetails gpProductionDetails = iGpProductionDetailsService.getById(gpProductionScheduling.getProductionDetailsId());
            if (gpProductionDetails != null) {
                int count = this.count(new LambdaQueryWrapper<GpProductionScheduling>().eq(GpProductionScheduling::getProductionDetailsId, gpProductionScheduling.getProductionDetailsId()).eq(GpProductionScheduling::getDelStatus, YesNoEnum.NO.getKey()));
                gpProductionScheduling.setSn(gpProductionDetails.getSn() + "-" + (count + 1));
            }
            this.save(gpProductionScheduling);
        }
        return true;
    }

    @Override
    public boolean splitOrders(Long id,Integer splitNum) {
        GpProductionScheduling gpProductionScheduling = this.getById(id);
        if (gpProductionScheduling == null) {
            return false;
        }
        //改变原有订单
        if (gpProductionScheduling.getStockGreyNum()==null){
            throw new BaseException("没有胚布库存剩余数量");
        }
        //改变原有订单
        if (gpProductionScheduling.getStockGreyNum()-splitNum<0){
            throw new BaseException("拆分的胚布库存剩余数量:"+splitNum+"大于原订单数:"+gpProductionScheduling.getStockGreyNum());
        }
        gpProductionScheduling.setLeaveGreyNum(gpProductionScheduling.getLeaveGreyNum()-splitNum);
        this.updateById(gpProductionScheduling);

        //String sn = gpProductionScheduling.getSn();
        //String newSn = "";
        //String[] split = sn.split("-");
        //if (split.length < 5){
        //    newSn = split[0] + "-" + split[1] + "-" + split[2] + "-" +  split[3] +"-"+1;
        //} else {
        //    newSn = split[0] + "-" + split[1] + "-" + split[2] + "-" + split[3] + "-" + (Integer.parseInt(split[4])+ 1);
        //}
        //新增拆分订单

        GpProductionScheduling addProductionScheduling = Convert.convert(new TypeReference<GpProductionScheduling>() {
        }, gpProductionScheduling);
        addProductionScheduling.setId(null);
        addProductionScheduling.setStockGreyNum(splitNum);
        addProductionScheduling.setLeaveGreyNum(splitNum);
        addProductionScheduling.setSn(null);
        this.save(addProductionScheduling);
        return true;
    }

    private void init(GpProductionScheduling gpProductionScheduling) {
        if (gpProductionScheduling.getReturnTime() != null) {
            // 生成胚布进仓批号
            if (StringUtils.isNotBlank(gpProductionScheduling.getSupplierName()) && gpProductionScheduling.getTotalWeight() != null) {
                String warehouseEntryNo = "";
                String MMdd = DateUtils.parseDateToStr("MMdd", gpProductionScheduling.getReturnTime());
                String initials = StringUtils.getPinYinHeadChar(gpProductionScheduling.getSupplierName());
                warehouseEntryNo += MMdd + "-" + initials + "-" + gpProductionScheduling.getTotalWeight();
                gpProductionScheduling.setWarehouseEntryNo(warehouseEntryNo);
            }
            // 计算时长（回货日期-下单日期）
            if (gpProductionScheduling.getPlaceOrdersTime() != null) {
                String datePoor = DateUtils.findDatePoor(gpProductionScheduling.getPlaceOrdersTime(), gpProductionScheduling.getReturnTime());
                gpProductionScheduling.setDuration(datePoor.split("-")[0]);
            }
        }
        // 计算胚布剩余重量
        if (gpProductionScheduling.getLeaveGreyNum() != null && gpProductionScheduling.getActualGreyUsed() != null) {


            int leaveGreyNum = gpProductionScheduling.getLeaveGreyNum() - gpProductionScheduling.getActualGreyUsed();
            gpProductionScheduling.setLeaveGreyNum(leaveGreyNum);

            GpProductionDetails gpProductionDetails = iGpProductionDetailsService.getById(gpProductionScheduling.getProductionDetailsId());
            //胚布剩余重量
            gpProductionDetails.setLeaveGreyNum(leaveGreyNum);
            iGpProductionDetailsService.updateById(gpProductionDetails);
        }
    }
}
